			RAM and ROM functions
			---------------------

I) RAM Adresses
---------------

1) The screen
-------------

The adress of the video memory is accessed with LCD_MEM, or $4c00.

example:	lea	LCD_MEM,a0	;a0 contains the adress


The screen is a 160*100 black and white LCD screen on the 89
The screen is a 240*128 black and white LCD screen on the 92 Plus
Each line is 30 bytes but only 20 are used on the 89.

You can get the most used screen values with:
	move.w	#LCD_LINE_BYTES,d0	;d0 contains #20 on a 89,#30 on a 92 Plus
	move.w	#LCD_WIDTH,d1		;d1=160 or 240
	move.w	#LCD_HEIGHT,d2		;d2=100 or 128
	move.w	#LCD_SIZE,d3		;d3=2000 or 3840

** Note that the video memory is still 3840 bytes on the 89 but only 2000 are used for display **

2) The keyboard
---------------

doorsos::kb_vars+$1C is the key flag: it is null if no key was pressed

doorsos::MaxHandles+$1E is the keycode word: nearly all are documented in
the manual but some are not documented or different.

doorsos::kb_vars+$1E is the keycode too, but when you let an arrow key
pressed for a short time, the value changes.

The function userlib::idle_loop waits for a key input and returns in d0
the keycode of the key pressed

We recommend that you use:

KEY_LEFT
KEY_RIGHT
KEY_UP
KEY_DOWN
KEY_UPRIGHT
KEY_DOWNLEFT

to get these keycodes because they are different on the 89 and on the 92 Plus.

What's more, to test if diamond or shift was pressed with non alphabetical
keys, you should use:
	cmp.w	#KEY_DIAMOND+xx,d0	;tests if d0 is the code of <diamond>+ a key which value is xx
or	cmp.w	#SHIFT+xx,d0	;tests if d0 is the code of <SHIFT>+ a key which value is xx

3) Heap
-------

We actually found 3 Heap variables:

* doorsos::MaxHandles is the number of handles the handle table can contain
* doorsos::Heap is the adress of the pointer to the handle table
* doorsos::TopHeap is the pointer to the top of Heap memory

4) APD
------

Here too 3 variables:

* APD_INIT	is the initial value of the APD (default: $1770 -> 300 sec -> 5 min)
* APD_TIMER	is the actual value of the timer
* APD_FLAG	is the APD flag: set when APD_TIMER becomes null.

5) Macros
---------

EXTRA_RAM_TABLE macro
_extraram:
    xdef _extraram
    endm

* This macro declares to the compiler that there is an Extra RAM table in your program.
An extra RAM table is a table which contains some variables you have found,
which are different on the 89 and the 92 Plus, and are not managed by the kernel.


EXTRA_RAM_ADDR macro
    dc.w \3
    dc.w \4
\2 equ _extraramaddr@\1
    endm

* This macro defines an extra RAM variable. Example:
	EXTRA_RAM_ADDR	0000,var,#10,#20
* 0000 is the index of the extra RAM variable. It is a 4 digit hex number.
* var is the name of this variable. You can access it in your file with:
	move.w	#var,d0	;d0=10 or 20
* #10 is the value on the 89, #20 the value on the 92 +


doorsos::DEREF     macro   ; Dn,An
	lsl.w	#2,\1
        move.l  doorsos::Heap,\2
	move.l	0(\2,\1.w),\2
		endm

* This macro has 2 parameters:
	\1 is a Dn register which contains a handle
	\2 is a An register which will receive the adress corresponding to the handle.

SetFont	macro
	move.w	\1,-(a7)
	jsr	doorsos::FontSetSys
	addq.l	#2,a7
		endm

* This macro has 1 parameter:
	\1 is the number of the font you want to set (0,1 or 2)

WriteStr	macro	;x,y,col,str
	move.w	\3,-(a7)
	pea	\4(pc)
	move.w	\2,-(a7)
	move.w	\1,-(a7)
	jsr	doorsos::DrawStrXY
	lea	10(a7),a7
                endm

* This macro has 4 parameters:
	\1	the x coordinate
	\2	the y coordinate
	\3	the color (0,1,2,3 or 4)
	\4	the label of the string to print

WriteStrA	macro	;x,y,col,An
	move.w	\3,-(a7)
	move.l	\4,-(a7)
	move.w	\2,-(a7)
	move.w	\1,-(a7)
	jsr	doorsos::DrawStrXY
	lea	10(a7),a7
                endm
* Same a WriteStr but the 4th parameter is an adress register, the pointer to the string.

6) Misc
-------
* CALCULATOR is a variable which indicates on which calculator the program
is actually running. (=0 on the 89, =1 on the 92 Plus)

For example, you can do
	tst.b	CALCULATOR
	beq	\89code
	(..)	;code for the 92 Plus

	...

\89code
	(..)	;code for the 89

* doorsos::HomeScreenEntryHandle is the pointer to the handle of the
Home Screen Entry.

* doorsos::ROM_base is the adress of the beginning of the ROM

II) ROM functions
-----------------

The ROM functions table is pointed to at $C8
The adress of the beginning of the ROM is doorsos::ROM_base

Note: Most of infos following are taken from David Ellsworth's Fargo doc.

;----------------------------------------------------------------------------
; Notes on ROM calls
;----------------------------------------------------------------------------
; Function parameters are listed using the C language calling convention.
; Parameters are pushed onto the stack in reverse order.
;
; To clean up after the function has been called, pop all the values that
; were pushed. This can be done by adding a value to SP; this value is
; calculated by summing the sizes of all the parameters that were pushed.
;
; Unless otherwise specified, assume that D0-D2/A0-A1 are destroyed by any
; given ROM function upon return.
;
; Inside a block of English text, variables will be
; designated with surrounding braces {}.
;----------------------------------------------------------------------------
;  BYTE =  8-bit unsigned integer
;  WORD = 16-bit unsigned integer
;  LONG = 32-bit unsigned integer
; SBYTE =  8-bit signed integer
; SWORD = 16-bit signed integer
; SLONG = 32-bit signed integer
;----------------------------------------------------------------------------


;----------------------------------------------------------------------------
; ER_throwVar(WORD errorNum)
;
; Function: Restores the state previously saved by ER_catch, making
;           D0.W = {errorNum}
;
; Return: Never returns
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; WORD ER_catch(void *ErrorFrame)
;
; Function: Saves the state in {ErrorFrame}, which is a $38 byte structure.
;           The state consists of the values of A2-A7, D3-D7, and PC. It also
;           records a pointer to the previously saved state, which makes it a
;           linked list / stack.
;
; Return: D0.W = 0
;
; Note: If ER_throw is called later on, it simulates a return from the
;       previously called ER_catch, in which D0.W = the error code. The
;       processor must be in User mode for this to work properly.
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; void ER_success(void)
;
; Function: Pops the state previously saved by ER_catch off the stack.
;----------------------------------------------------------------------------

;============================================================================
; Error Dialog functions
;============================================================================

;----------------------------------------------------------------------------
; void ERD_dialog(WORD errorNum)
;
; Function: Displays an error dialog box with a message corresponding to the
;           error code {errorNum}.
;----------------------------------------------------------------------------

;============================================================================
; Status line functions
;============================================================================

;----------------------------------------------------------------------------
; void ST_busy(WORD mode)
;
; Function: Switches to idle, busy, or paused. This indicator is displayed
;           in the status line. You must call update_status() for the change
;           to appear visually.
;
; mode=0 -> idle
; mode=1 -> busy
; mode=2 -> paused
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; void ST_eraseHelp(void)
;
; Function: If the status flags indicate that a help message is being
;           displayed, this function redraws the status line, effectively
;           removing the message.
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; void ST_showHelp(BYTE *message)
;
; Function: Displays {message} in the status line, also setting a status
;           flag indicating that a message is being displayed.
;----------------------------------------------------------------------------

;============================================================================
; Heap functions
;============================================================================

;----------------------------------------------------------------------------
; void HeapFreeIndir(WORD *handle)
;
; Function: Deletes the allocated memory block {handle} and sets it to zero.
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; void HeapFree(WORD handle)
;
; Function: Deletes the allocated memory block {handle}.
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; WORD HeapAlloc(LONG size)
;
; Function: Allocates a memory handle.
;
; Return: success: D0.W = allocated handle
;         failure: D0.L = 0
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; WORD HeapAllocThrow(LONG size)
;
; Function: Allocates a memory handle, and does an ER_throw(ER_MEMORY) if
;           there's not enough RAM available.
;
; Return: D0.W = allocated handle
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; WORD HeapRealloc(WORD handle, LONG newsize)
;
; Function: Allocates or resizes a memory handle.
;
; Return: D0.W = reallocated handle (successful)
;         D0.L = 0 (unsuccessful)
;
; Note: If {handle} is zero, a new handle will be
;       created. Otherwise, {handle} will be
;       reallocated to the new size.
;----------------------------------------------------------------------------


;============================================================================
; Link transfer functions
;============================================================================

;----------------------------------------------------------------------------
; void reset_link(void)
;
; Function: resets the link interface
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; WORD tx_free(void)
;
; Function: returns the number of free bytes in the link transmit buffer
;
; Return: D0.W = number of bytes
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; transmit(BYTE *buffer, WORD num)
;
; Function: inserts {num} bytes from {buffer} into link transmit buffer
;
; Return: No error: D0.L = $00000000
;                   A0   = data + num
;         Error:    D0.B = $FF
;                   A0   = data
;
; {num} must be in the range [$01...$80]
;
; Note: An error occurs if {num} is out of range or if there is not enough
;       room in the transmit buffer to insert {num} bytes.
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; receive(BYTE *buffer, WORD num)
;
; Function: reads at most {num} bytes into {buffer} from link receive buffer
;
; Return:  D0.L = number of bytes read
;          A0 = buffer + (number of bytes read)
;----------------------------------------------------------------------------


;============================================================================
; Graphics functions
;============================================================================

;----------------------------------------------------------------------------
; void DrawStrXY(WORD x, WORD y, BYTE *string, WORD color)
;
; Function: prints {string} at {x,y} with current font
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; BYTE FontSetSys(BYTE font)
;
; Function: sets the current system font to {font}
;
; Return: D0.B = font before function was called
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; BYTE FontGetSys(void)
;
; Function: returns the current system font
;
; Return: D0.B = current font
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; void DrawTo(WORD x, WORD y)
;
; Function: Draws a line from the graphics cursor to {x,y}, moving the
;           graphics cursor to the new position.
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; void MoveTo(WORD x, WORD y)
;
; Function: Moves the graphics cursor to {x,y}
;----------------------------------------------------------------------------


;============================================================================
; Window functions
;============================================================================

;----------------------------------------------------------------------------
; WinActivate(WINDOW *window)
;
; Function: Draws {window} as created by WinOpen()
;
; Return: nothing
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; WinClose(WINDOW *window)
;
; Function: Replaces background and frees memory used by {window}
;
; Return: nothing
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; WinOpen(WINDOW *window, RECT *rect, WORD flags[, BYTE *title])
;
; Function: Creates a window descriptor at {window}.
;
; Return: success: D0.L = nonzero
;         failure: D0.L = zero
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; void WinStrXY(WINDOW *window, WORD x, WORD y, BYTE *string)
;
; Function: prints {string} to {window} at {x,y}
;
; Return: nothing
;----------------------------------------------------------------------------


;============================================================================
; C library functions
;----------------------------------------------------------------------------
;         int = 16-bit signed integer
;      size_t = 32-bit unsigned integer
;----------------------------------------------------------------------------
;        char =  8-bit signed integer
; short [int] = 16-bit signed integer
;  long [int] = 32-bit signed integer
;============================================================================

;----------------------------------------------------------------------------
; int sprintf(char *buffer, char *format[, argument, ...])
;
; Function: Uses {format} as a template to output a string to {buffer},
;           substituting arguments when '%' is found in {format}.
;
; Return: D0.W = number of bytes output
;
; For an explanation of format specifiers, please see a reference on the
; C programming language.
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; int strcmp(char *s1, char *s2)
;
; Function: Compares strings {s1} and {s2}.
;
; Return: D0.W < 0  if  s1 < s2
;         D0.W = 0  if  s1 = s2
;         D0.W > 0  if  s1 > s2
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; size_t strlen(char *s)
;
; Function: Calculates the length of the string {s}, not including the
;           terminating null character.
;
; Return: D0.L = length of string
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; int strncmp(char *s1, char *s2, size_t n)
;
; Function: Compares at most {n} characters of strings {s1} and {s2}.
;
; Return: D0.W < 0  if  s1 < s2
;         D0.W = 0  if  s1 = s2
;         D0.W > 0  if  s1 > s2
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; char *strncpy(char *dest, char *src, size_t n)
;
; Function: Copies the first {n} characters of string {src} into {dest}. In
;           the case where the length of {src} is less than {n}, the
;           remainder of {dest} will be padded with nulls.
;
; Return: A0 = {dest}
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; char *strcat(char *dest, char *src)
;
; Function: Appends the {src} string to the {dest} string, overwriting the
;           null character at the end of {dest}, and adding a terminating
;           null character at the end of the new string. The strings may not
;           overlap, and the {dest} string must have enough space for the
;           result.
;
; Return: A0 = {dest}
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; char *strchr(char *s, int c)
;
; Function: Returns a pointer to the first occurrence of the character {c} in
;           the string {s}.
;
; Return: A0 = pointer to first occurence of {c}
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; void *memset(void *s, int c, size_t n)
;
; Function: Fills the first {n} bytes of the memory area pointed to by {s}
;           with the constant byte {c}.
;
; Return: A0 = pointer to the memory area {s}
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; int memcmp(void *s1, void *s2, size_t n)
;
; Function: Compares the first {n} bytes of the memory areas {s1} and {s2}.
;
; Return: D0.W < 0  if  s1 < s2
;         D0.W = 0  if  s1 = s2
;         D0.W > 0  if  s1 > s2
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; void *memcpy(void *dest, void *src, size_t n)
;
; Function: Copies {n} bytes from memory area {src} to memory area {dest}.
;           The memory areas may not overlap. Use memmove() if the memory
;           areas do overlap.
;
; Return: A0 = pointer to the memory area {dest}
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; void *memmove(void *dest, void *src, size_t n)
;
; Function: Copies {n} bytes from memory area {src} to memory area {dest}.
;           The memory areas may overlap.
;
; Return: A0 = pointer to the memory area {dest}
;----------------------------------------------------------------------------


;============================================================================
; C hidden math functions
;============================================================================

;----------------------------------------------------------------------------
; _du32u32(): 32-bit unsigned division
;
; Input: D0.L = unsigned integer "x"
;        D1.L = unsigned integer "y"
;
; Output: D1.L = y / x
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; _ds32s32(): 32-bit signed division
;
; Input: D0.L = signed integer "x"
;        D1.L = signed integer "y"
;
; Output: D1.L = y / x
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; _du16u16(): 16-bit unsigned division
;
; Input: D0.W = unsigned integer "x"
;        D1.W = unsigned integer "y"
;
; Output: D1.W = y / x
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; _ds16u16(): 16-bit mixed-sign division
;
; Input: D0.W = signed integer "x"
;        D1.W = unsigned integer "y"
;
; Output: D1.W = y / x
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; _ru32u32(): 32-bit unsigned modulo (remainder of division)
;
; Input: D0.L = unsigned integer "x"
;        D1.L = unsigned integer "y"
;
; Output: D1.L = y % x
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; _rs32s32(): 32-bit signed modulo (remainder of division)
;
; Input: D0.L = signed integer "x"
;        D1.L = signed integer "y"
;
; Output: D1.L = y % x
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; _ru16u16(): 16-bit unsigned modulo (remainder of division)
;
; Input: D0.W = signed integer "x"
;        D1.W = signed integer "y"
;
; Output: D1.W = y % x
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; _rs16u16(): 16-bit mixed-sign modulo (remainder of division)
;
; Input: D0.W = signed integer "x"
;        D1.W = unsigned integer "y"
;
; Output: D1.W = y % x
;----------------------------------------------------------------------------

;============================================================================
; Archive Functions
;============================================================================

;----------------------------------------------------------------------------
; ArchiveErase(LONG sectoradress)
;
; Function: Erases the 64k Archive sector pointed to by sectoradress
;----------------------------------------------------------------------------

;----------------------------------------------------------------------------
; ArchiveWrite(CHAR* buffer, LONG sectoradress, LONG size)
;
; Function: Writes <size> bytes from buffer to sectoradress
;----------------------------------------------------------------------------
